package com.zzh.lib.views.drawer;


import android.graphics.Canvas;
import android.graphics.RectF;

import com.zzh.lib.views.banner.IndicatorOptions;
import com.zzh.lib.views.def.IndicatorSlideMode;
import com.zzh.lib.views.utils.BannerUtils;

/**
 * Created by ZZH on 2023/2/16.
 *
 * @date: 2023/2/16 09:44
 * @email: zzh_hz@126.com
 * @author: zzh
 * @description: com.zzh.lib.views.drawer
 */
public class RectDrawer extends BaseDrawer {
    protected RectF mRectF = new RectF();

    public RectDrawer(IndicatorOptions indicatorOptions) {
        super(indicatorOptions);
    }

    @Override
    public void onDraw(Canvas canvas) {

        int pageSize = mIndicatorOptions.getPageSize();
        if (pageSize > 1 || mIndicatorOptions.showIndicatorOneItem && pageSize == 1) {
            if (isWidthEquals() && mIndicatorOptions.getSlideMode() != IndicatorSlideMode.NORMAL) {
                drawUncheckedSlider(canvas, pageSize);
                drawCheckedSlider(canvas);
            } else {    // 单独处理normalWidth与checkedWidth不一致的情况
                if (mIndicatorOptions.getSlideMode() == IndicatorSlideMode.SCALE) {
                    for (int i = 0; i < pageSize; i++) {
                        drawScaleSlider(canvas, i);
                    }
                } else {
                    drawInequalitySlider(canvas, pageSize);
                }
            }
        }
    }

    private void drawScaleSlider(Canvas canvas, int i) {
        int checkedColor = mIndicatorOptions.getCheckedSliderColor();
        float indicatorGap = mIndicatorOptions.getSliderGap();
        float sliderHeight = mIndicatorOptions.getSliderHeight();
        int currentPosition = mIndicatorOptions.getCurrentPosition();
        float normalWidth = mIndicatorOptions.getNormalSliderWidth();
        float checkedWidth = mIndicatorOptions.getCheckedSliderWidth();

        if (i < currentPosition) {
            mPaint.setColor(mIndicatorOptions.getNormalSliderColor());
            float left;
            if (currentPosition == mIndicatorOptions.pageSize - 1) {
                left = (i * normalWidth + i * indicatorGap) + (checkedWidth - normalWidth) * mIndicatorOptions.slideProgress;
            } else {
                left = (i * normalWidth + i * indicatorGap);
            }
            mRectF.set(left, 0f, left + normalWidth, sliderHeight);
            drawRoundRect(canvas, sliderHeight, sliderHeight);
        } else if (i == currentPosition) {
            mPaint.setColor(checkedColor);
            float slideProgress = mIndicatorOptions.slideProgress;
            if (currentPosition == mIndicatorOptions.pageSize - 1) {
                float evaluate = Float.parseFloat(argbEvaluator.evaluate(slideProgress, checkedColor, mIndicatorOptions.normalSliderColor).toString());
                mPaint.setColor((int) evaluate);
                float right =
                        (mIndicatorOptions.pageSize - 1) * (normalWidth + mIndicatorOptions.sliderGap) + checkedWidth;
                float left = right - checkedWidth + (checkedWidth - normalWidth) * (slideProgress);
                mRectF.set(left, 0f, right, sliderHeight);
                drawRoundRect(canvas, sliderHeight, sliderHeight);
            } else {
                if (slideProgress < 1) {
                    float evaluate = (Float) argbEvaluator.evaluate(
                            slideProgress, checkedColor, mIndicatorOptions.normalSliderColor
                    );
                    mPaint.setColor((int) evaluate);
                    float left = i * normalWidth + i * indicatorGap;
                    float right = left + normalWidth + (checkedWidth - normalWidth) * (1 - slideProgress);
                    mRectF.set(left, 0f, right, sliderHeight);
                    drawRoundRect(canvas, sliderHeight, sliderHeight);
                }
            }

            if (currentPosition == mIndicatorOptions.pageSize - 1) {
                if (slideProgress > 0) {
                    float evaluate = (float) argbEvaluator.evaluate(
                            1 - slideProgress, checkedColor, mIndicatorOptions.normalSliderColor
                    );
                    mPaint.setColor((int) evaluate);
                    float left = 0f;
                    float right = left + normalWidth + (checkedWidth - normalWidth) * slideProgress;

                    mRectF.set(left, 0f, right, sliderHeight);
                    drawRoundRect(canvas, sliderHeight, sliderHeight);
                }
            } else {
                if (slideProgress > 0) {
                    float evaluate = (float) argbEvaluator.evaluate(1 - slideProgress, checkedColor, mIndicatorOptions.normalSliderColor);
                    mPaint.setColor((int) evaluate);
                    float right = i * normalWidth + i * indicatorGap + normalWidth + (indicatorGap + checkedWidth);
                    float left = right - (normalWidth) - (checkedWidth - normalWidth) * (slideProgress);
                    mRectF.set(left, 0f, right, sliderHeight);
                    drawRoundRect(canvas, sliderHeight, sliderHeight);
                }
            }
        } else {
            if ((currentPosition + 1 != i || mIndicatorOptions.slideProgress == 0f)) { // 避免多余绘制
                mPaint.setColor(mIndicatorOptions.normalSliderColor);
                float left = i * minWidth + i * indicatorGap + (checkedWidth - minWidth);
                mRectF.set(left, 0f, left + minWidth, sliderHeight);
                drawRoundRect(canvas, sliderHeight, sliderHeight);
            }
        }
    }

    private void drawUncheckedSlider(
            Canvas canvas,
            int pageSize
    ) {
        for (int i = 0; i < pageSize; i++) {
            mPaint.setColor(mIndicatorOptions.normalSliderColor);
            float left = i * maxWidth + i * +mIndicatorOptions.sliderGap + (maxWidth - minWidth);
            mRectF.set(left, 0f, left + minWidth, mIndicatorOptions.sliderHeight);
            drawRoundRect(canvas, mIndicatorOptions.sliderHeight, mIndicatorOptions.sliderHeight);
        }
    }

    private void drawInequalitySlider(
            Canvas canvas,
            int pageSize
    ) {
        var left = 0f;
        for (int i = 0; i < pageSize; i++) {
            float sliderWidth = 0f;
            if (i == mIndicatorOptions.currentPosition) {
                sliderWidth = maxWidth;
            } else {
                sliderWidth = minWidth;
            }

            if (i == mIndicatorOptions.currentPosition) {
                mPaint.setColor(mIndicatorOptions.checkedSliderColor);
            } else {
                mPaint.setColor(mIndicatorOptions.normalSliderColor);
            }
            mRectF.set(left, 0f, left + sliderWidth, mIndicatorOptions.sliderHeight);
            drawRoundRect(canvas, mIndicatorOptions.sliderHeight, mIndicatorOptions.sliderHeight);
            left += sliderWidth + mIndicatorOptions.sliderGap;
        }
    }

    private void drawCheckedSlider(Canvas canvas) {
        mPaint.setColor(mIndicatorOptions.checkedSliderColor);
        switch (mIndicatorOptions.slideMode) {
            case IndicatorSlideMode.SMOOTH:
                drawSmoothSlider(canvas);
                break;
            case IndicatorSlideMode.WORM:
                drawWormSlider(canvas);
                break;
            case IndicatorSlideMode.COLOR:
                drawColorSlider(canvas);
                break;
        }
    }

    private void drawColorSlider(Canvas canvas) {
        int currentPosition = mIndicatorOptions.currentPosition;
        float slideProgress = mIndicatorOptions.slideProgress;
        float left = currentPosition * minWidth + currentPosition * mIndicatorOptions.sliderGap;
        if (slideProgress < 0.99) {
            float evaluate = (float) argbEvaluator.evaluate(slideProgress, mIndicatorOptions.checkedSliderColor, mIndicatorOptions.normalSliderColor);
            mPaint.setColor((int) evaluate);
            mRectF.set(left, 0f, left + minWidth, mIndicatorOptions.sliderHeight);
            drawRoundRect(canvas, mIndicatorOptions.sliderHeight, mIndicatorOptions.sliderHeight);
        }

        float nextSliderLeft = left + mIndicatorOptions.sliderGap + mIndicatorOptions.normalSliderWidth;
        if (currentPosition == mIndicatorOptions.pageSize - 1) {
            nextSliderLeft = 0f;
        }
        float evaluate = (float) argbEvaluator.evaluate(1 - slideProgress, mIndicatorOptions.checkedSliderColor, mIndicatorOptions.normalSliderColor);
        mPaint.setColor((int) evaluate);
        mRectF.set(nextSliderLeft, 0f, nextSliderLeft + minWidth, mIndicatorOptions.sliderHeight);
        drawRoundRect(canvas, mIndicatorOptions.sliderHeight, mIndicatorOptions.sliderHeight);
    }

    private void drawWormSlider(Canvas canvas) {
        float sliderHeight = mIndicatorOptions.sliderHeight;
        float slideProgress = mIndicatorOptions.slideProgress;
        int currentPosition = mIndicatorOptions.currentPosition;
        float distance = mIndicatorOptions.sliderGap + mIndicatorOptions.normalSliderWidth;
        float startCoordinateX =
                BannerUtils.getCoordinateX(mIndicatorOptions, maxWidth, currentPosition);
        float coerceAtLeast = distance * (slideProgress - 0.5f) * 2.0f;
        if (coerceAtLeast < 0) {
            coerceAtLeast = 0;
        }
        float left = startCoordinateX + coerceAtLeast - mIndicatorOptions.normalSliderWidth / 2;


        float vDis = distance * slideProgress * 2f;
        if (vDis > distance) {

            vDis = distance;
        }
        float right = startCoordinateX + vDis + mIndicatorOptions.normalSliderWidth / 2;
        mRectF.set(left, 0f, right, sliderHeight);
        drawRoundRect(canvas, sliderHeight, sliderHeight);
    }

    protected void drawSmoothSlider(Canvas canvas) {
        int currentPosition = mIndicatorOptions.currentPosition;
        float indicatorGap = mIndicatorOptions.sliderGap;
        float sliderHeight = mIndicatorOptions.sliderHeight;
        float left =
                currentPosition * maxWidth + currentPosition * +indicatorGap + (maxWidth + indicatorGap) * mIndicatorOptions.slideProgress;
        mRectF.set(left, 0f, left + maxWidth, sliderHeight);
        drawRoundRect(canvas, sliderHeight, sliderHeight);
    }

    protected void drawRoundRect(Canvas canvas, float rx, float ry) {
        drawDash(canvas);
    }

    protected void drawDash(Canvas canvas) {

    }
}
